package Chart;

import java.awt.Color;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowEvent;
import java.io.File;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Map.Entry;
import java.util.ResourceBundle;

import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.JFileChooser;
import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;

import org.jfree.chart.ChartFactory;
import org.jfree.chart.ChartPanel;
import org.jfree.chart.ChartUtilities;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.axis.DateAxis;
import org.jfree.chart.plot.XYPlot;
import org.jfree.chart.renderer.xy.XYItemRenderer;
import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer;
import org.jfree.chart.util.ResourceBundleWrapper;
import org.jfree.data.time.Day;
import org.jfree.data.time.Hour;
import org.jfree.data.time.Minute;
import org.jfree.data.time.TimeSeries;
import org.jfree.data.time.TimeSeriesCollection;
import org.jfree.data.xy.XYDataset;
import org.jfree.ui.ApplicationFrame;
import org.jfree.ui.ExtensionFileFilter;
import org.jfree.ui.RectangleInsets;
import org.jfree.ui.RefineryUtilities;

@SuppressWarnings("serial")
public class TimeChart extends ApplicationFrame implements ActionListener {
	// ten file lay tu open file
	static String filename = File.separator;
	private static String selectedPath;

	protected static ResourceBundle localizationResources = ResourceBundleWrapper
			.getBundle("org.jfree.chart.LocalizationBundle");

	/** A flag that controls whether or not file extensions are enforced. */
	private boolean enforceFileExtensions;

	static JFreeChart chart;

	/**
	 * A demonstration application showing how to create a simple time series
	 * chart.
	 * 
	 * @param title
	 *            the frame title.
	 */
	public TimeChart(String title) throws IOException {
		super(title);
		setPreferredSize(new java.awt.Dimension(800, 600));
		// menu
		JFileChooser fc = new JFileChooser(new File(filename));
		// khoi tao openaction
		Action openAction = new OpenFileAction(this, fc);
		Action saveAction = new SaveFileAction(this, fc);

		JMenuBar mb = new JMenuBar();

		JMenu jFile = new JMenu("File");
		mb.add(jFile);

		// tao item menu Open...
		JMenuItem jOpen = new JMenuItem(openAction);
		jFile.add(jOpen);

		JMenuItem jSave = new JMenuItem(saveAction);
		jFile.add(jSave);

		JMenuItem jExit = new JMenuItem("Exit");
		jFile.add(jExit);
		jExit.addActionListener(this);

		// create menu Edit
		JMenu jEdit = new JMenu("Edit");
		mb.add(jEdit);

		// create item menu Edit

		// create Properties
		JMenuItem jProperties = new JMenuItem("Properties...");
		jEdit.add(jProperties);
		jProperties.addActionListener(this);

		this.setJMenuBar(mb);
		this.addWindowListener(this);
		this.enforceFileExtensions = true;
	}

	public void actionPerformed(ActionEvent ae) {
		if (ae.getActionCommand().equals("Exit")) {
			Main demo = new Main("Demo");
			demo.pack();
			RefineryUtilities.centerFrameOnScreen(demo);
			demo.setVisible(true);
		} else if (ae.getActionCommand().equals("Properties...")) {
			ChartPanel chartPanel = (ChartPanel) createPanel();
			chartPanel.doEditChartProperties();
		}
	}

	public void windowClosing(WindowEvent e) {
		Main demo = new Main("Demo");
		demo.pack();
		RefineryUtilities.centerFrameOnScreen(demo);
		demo.setVisible(true);
	}

	/**
	 * Creates a chart.
	 * 
	 * @param dataset
	 *            a dataset.
	 * 
	 * @return A chart.
	 */
	private static JFreeChart createChart(XYDataset dataset) {
		chart = ChartFactory.createTimeSeriesChart("ChartUser", "Minute",
				"Number of User", dataset, true, true, false);
		chart.setBackgroundPaint(Color.white);

		XYPlot plot = (XYPlot) chart.getPlot();
		plot.setBackgroundPaint(Color.lightGray);
		plot.setDomainGridlinePaint(Color.blue);
		plot.setRangeGridlinePaint(Color.blue);
		plot.setAxisOffset(new RectangleInsets(5.0, 5.0, 5.0, 5.0));
		plot.setDomainCrosshairVisible(true);
		plot.setRangeGridlinesVisible(true);

		XYItemRenderer r = plot.getRenderer();
		if (r instanceof XYLineAndShapeRenderer) {
			XYLineAndShapeRenderer renderer = (XYLineAndShapeRenderer) r;
			renderer.setBaseShapesVisible(true);
			renderer.setBaseShapesFilled(true);
		}

		DateAxis axis = (DateAxis) plot.getDomainAxis();
		axis.setDateFormatOverride(new SimpleDateFormat("hh:mm:ss"));
		return chart;
	}

	/**
	 * Creates a dataset.
	 * 
	 * @return the dataset.
	 */
	@SuppressWarnings("deprecation")
	public static XYDataset createDataset() throws IOException {

		TimeSeries series = new TimeSeries("Minute Data", Minute.class);
		ReadData rd = new ReadData(selectedPath);
		if (selectedPath == null) {
			JFrame frame = new JFrame("Warning");
			JOptionPane.showMessageDialog(frame,
					" You can't show chart! Please click File/Open...!",
					"Warning", JOptionPane.WARNING_MESSAGE);
		} else {
			rd.ReadofTimeChart();
			int dDay = 0;
			int dMonth = 0;
			int dYear = 0;
			int dHour = 0;
			int dMinute = 0;
			for (Entry<String, Double> entry : rd.dataAverage.entrySet()) {
				String key = entry.getKey();
				dDay = Integer.valueOf(key.substring(3, 5));
				dMonth = Integer.valueOf(key.substring(0, 2));
				dYear = Integer.valueOf(key.substring(6, 10));
				dHour = Integer.valueOf(key.substring(11, 13));
				dMinute = Integer.valueOf(key.substring(14, 16));
				Day day = new Day(dDay, dMonth, dYear);
				Hour hour = new Hour(dHour, day);
				series.addOrUpdate(new Minute(dMinute, hour), entry.getValue());
			}
		}
		TimeSeriesCollection dataset = new TimeSeriesCollection();
		dataset.addSeries(series);
		dataset.setDomainIsPointsInTime(true);

		return dataset;
	}

	public JPanel createPanel() {
		try {
			chart = createChart(createDataset());
		} catch (IOException e) {
			e.printStackTrace();
		}
		ChartPanel chartPanel = new ChartPanel(chart);
		chartPanel.setPreferredSize(new java.awt.Dimension(800, 600));
		chartPanel.setMouseZoomable(true, false);
		setContentPane(chartPanel);
		SwingUtilities.updateComponentTreeUI(getLayeredPane());
		return chartPanel;
	}

	class OpenFileAction extends AbstractAction {

		JFrame frame;
		JFileChooser chooser;

		public OpenFileAction(JFrame frame, JFileChooser chooser) {
			super("Open...");
			this.chooser = chooser;
			this.frame = frame;

		}

		@Override
		public void actionPerformed(ActionEvent e) {
			// Show dialog; this method does not return until dialog is closed
			int option = chooser.showOpenDialog(frame);
			if (option == JFileChooser.APPROVE_OPTION) {

				// Get the selected file
				selectedPath = chooser.getSelectedFile().getPath();

			}
			createPanel();
		}
	}

	public boolean isEnforceFileExtensions() {
		return this.enforceFileExtensions;
	}

	class SaveFileAction extends AbstractAction {

		JFrame jFrame;
		JFileChooser chooser;
		private File defaultDirectoryForSaveAs;

		public SaveFileAction(JFrame jFrame, JFileChooser chooser) {
			super("Save As...");
			this.jFrame = jFrame;
			this.chooser = chooser;
		}

		@Override
		public void actionPerformed(ActionEvent arg0) {

			chooser.setCurrentDirectory(this.defaultDirectoryForSaveAs);
			ExtensionFileFilter filter = new ExtensionFileFilter(
					((ResourceBundle) localizationResources)
							.getString("PNG_Image_Files"),
					".png");
			chooser.addChoosableFileFilter(filter);

			XYDataset dataset = null;
			try {
				dataset = createDataset();
			} catch (IOException e1) {
				e1.printStackTrace();
			}

			JFreeChart chart = createChart(dataset);

			int option = chooser.showSaveDialog(jFrame);
			if (option == JFileChooser.APPROVE_OPTION) {
				String filename = chooser.getSelectedFile().getPath();
				if (isEnforceFileExtensions()) {
					if (!filename.endsWith(".png")) {
						filename = filename + ".png";
					}
				}
				try {
					ChartUtilities.saveChartAsPNG(new File(filename), chart,
							getWidth(), getHeight());
				} catch (IOException e) {
					e.printStackTrace();
				}
			}
		}

	}
}
